#!/usr/bin/env python 
# -*- coding:utf-8 -*-

import time

from utils.log import log
from ziroom.client import api
from ziroom.dao import dao


class service(object):
    # 地图基础信息
    __min_lng = 115.948379
    __max_lng = 116.859621
    __min_lat = 39.716147
    __max_lat = 40.113273
    __dao = dao.dao()
    __api = api.api()
    __log = log.getLog('zr')

    # 求出经纬度增量
    def __get_lnglat_incr(self, zoom=12, min_lng=__min_lng, max_lng=__max_lng, min_lat=__min_lat, max_lat=__max_lat):
        sub_lng = max_lng - min_lng
        sub_lat = max_lat - min_lat
        def_zoom = 12
        temp = 1
        if zoom >= def_zoom:
            temp = 2 ** (zoom - def_zoom)
        return float('%.6f' % (sub_lng / 2 / temp)), float('%.6f' % (sub_lat / 2 / temp))

    # 求出区域范围
    def __get_range(self, lng, lat, lng_incr, lat_incr):
        min_lng = lng - lng_incr
        max_lng = lng + lng_incr
        min_lat = lat - lat_incr
        max_lat = lat + lat_incr
        return float('%.6f' % (min_lng)), float('%.6f' % (max_lng)), float('%.6f' % (min_lat)), float('%.6f' % (max_lat))

    # 获取区域中心点（包括补充中心）
    def __get_additional(self, lng, lat, lng_incr, lat_incr, count = 1):
        mlist = []
        for i in range(-count, count + 1):
            for j in range(-count, count + 1):
                x = lng_incr * i
                y = lat_incr * j
                item = float('%.6f' % (lng + x)), float('%.6f' % (lat + y))
                mlist.append(item)
        return mlist

    # 遍历小区信息
    def __iterate_list(self, min_lng, max_lng, min_lat, max_lat, clng, clat, zoom, parentCode=0):
        dataList = self.__api.getCountList(min_lng, max_lng, min_lat, max_lat, clng, clat, zoom)
        if dataList:
            self.__log.info("> zoom:【{}】-- dataList size:【{}】".format(zoom, len(dataList)))
            for item in dataList:
                # 保存额外信息
                item['zoom'] = zoom
                item['pCode'] = parentCode
                self.__dao.update_region(item)
                if zoom < 16:
                    longitude = float(item['longitude'])
                    latitude = float(item['latitude'])
                    # 求出下级范围
                    (sub_lng, sub_lat) = self.get_increment(min_lng, max_lng, min_lat, max_lat, zoom + 2)
                    (min_lng2, max_lng2, min_lat2, max_lat2) = self.__get_range(longitude, latitude, sub_lng, sub_lat)
                    # 遍历下级内容
                    self.__iterate_list(min_lng2, max_lng2, min_lat2, max_lat2, longitude, latitude, zoom + 2, code)

            print(" ")

    # 查询指定地区
    def __build_geo_info(self, clng14, clat14, code):
        zoom = 16

        def build(lng, lat):
            (min_lng, max_lng, min_lat, max_lat) = self.__get_range(lng, lat, lng_incr16, lat_incr16)
            return self.__iterate_list(min_lng, max_lng, min_lat, max_lat, lng, lat, zoom, code)

        # zoom16的经纬度增量
        (lng_incr16, lat_incr16) = self.__get_lnglat_incr(zoom=zoom)
        # 获取包含误差补充地区中心点坐标
        mlist = self.__get_additional(clng14, clat14, lng_incr16, lat_incr16, 2)
        for (x, y) in mlist:
            build(x, y)

    # 获取数据库中二级地区
    def region_update_task(self, zoom=14):
        lt = self.__dao.find_list_byzoom(zoom, sort={'code': 1})
        if lt:
            for item in lt:
                if item:
                    clng = float(item['longitude'])
                    clat = float(item['latitude'])
                    code = float(item['code'])
                    self.__build_geo_info(clng, clat, code)
                    time.sleep(2)

    def __get_room_list_page(self, lng, lat, lng_incr, lat_incr, code=None):
        (min_lng, max_lng, min_lat, max_lat) = self.__get_range(lng, lat, lng_incr, lat_incr)
        datalist = ['t']
        page = 1
        total_page = 1
        while len(datalist) > 0 and page <= total_page:
            data = self.__api.getList(min_lng, max_lng, min_lat, max_lat, lng, lat, 16, page, resblock_id=code)
            datalist = data['rooms']
            total_page = int(data['pages'])
            total = int(data['total'])
            self.__log.info("[{}/{}] 房屋分页查询 total={}".format(page, total_page, total))
            for item in datalist:
                self.__dao.update_room(item)
            # print(">> 房屋保存完毕")
            page += 1
            time.sleep(1)

    def room_update_task(self, skip=None):
        sort = {'code': 1}
        lt = self.__dao.find_list_byzoom(16, sort=sort, skip=skip)
        if lt:
            total = lt.count()
            for index, item in enumerate(lt):
                if item:
                    clng = float(item['longitude'])
                    clat = float(item['latitude'])
                    code = item['code']
                    name = item['name']
                    (lng_incr16, lat_incr16) = self.__get_lnglat_incr(zoom=16)
                    mlist = self.__get_additional(clng, clat, lng_incr16, lat_incr16, 0)
                    index_str = index
                    total_str = total
                    if skip is not None:
                        index_str = "{}({})".format(index, index + int(skip))
                        total_str = "{}({})".format(total - int(skip) - 1, total)
                    self.__log.info("---- [{}/{}] - [{}] - 查询开始 code={}".format(index_str, total_str, name, code))
                    for (lng, lat) in mlist:
                        self.__get_room_list_page(lng, lat, lng_incr16, lat_incr16, code=code)
                    self.__log.info("---- [{}] - 查询完毕 code={}".format(name, code))
                    time.sleep(1)


# test
if __name__ == "__main__":
    service = service()
    min_lng = 115.948379
    max_lng = 116.859621
    min_lat = 39.716147
    max_lat = 40.113273
    clng = 116.404
    clat = 39.915
    # 查询指定地区
    # clng14 = 116.375836
    # clat14 = 39.794509

    # lng_incr16, lat_incr16 = service.__get_lnglat_incr(min_lng, max_lng, min_lat, max_lat, 16)
    # print("lng = {}, lat ={}".format(lng_incr16, lat_incr16))

    # 核心区域
    # min_lng16, max_lng16, min_lat16, max_lat16 = get_range(clng14, clat14, lng_incr16, lat_incr16)
    # service.iterate_list(min_lng16, max_lng16, min_lat16, max_lat16, clng14, clat14, 16)
    # 补充点
    mlist = service.get_additional(116, 39, 0.1, 0.1, count = 0)
    for (x, y) in mlist:
        print("x = {}, y = {}".format(x, y))
    #     min_lng161, max_lng161, min_lat161, max_lat161 = service.get_range(x, y, lng_incr16, lat_incr16)
        # iterate_list(min_lng161, max_lng161, min_lat161, max_lat161, x, y, 16, 18335751)
